package basic;

import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;

/**
 * @Description: TODO java反射demo
 * @Author: wzj
 * @Date: 2020/11/21 9:32
 */
public class ReflectDemo {
    public static void main(String[] args) {
        try {
            ReflectObj reflectObj=new ReflectObj("new的对象");
            Class clazz=reflectObj.getClass();
            //方法
            System.out.println("~~~ 方法 ~~~");
            Method method0=clazz.getDeclaredMethod("print");
            Method method1=clazz.getDeclaredMethod("setName", String.class);
            Method method2=clazz.getDeclaredMethod("getName");
            method0.invoke(reflectObj);
            method1.invoke(reflectObj,"invoke参数");
            String name=(String)method2.invoke(reflectObj);
            System.out.println("getName返回 "+name);
            //属性
            System.out.println("~~~ 属性 ~~~");
            Field field0=clazz.getField("namePublic");//getField只能获取public字段，否则报异常java.lang.NoSuchFieldException
            System.out.println("public字段 "+field0.getName());
            Field field1=clazz.getDeclaredField("name");//getDeclaredField获取所有类型字段
            field1.setAccessible(true);//私有属性设置可访问
            field1.set(reflectObj,"字段设置属性值");
            method0.invoke(reflectObj);
            System.out.println(field1.getName());
            //通过反射生成对象
            System.out.println("~~~ 通过反射生成对象 ~~~");
            Class clazz1=Class.forName("basic.ReflectObj");
            ReflectObj reflectObj1=(ReflectObj)clazz1.newInstance();//获取无参数的构造方法
            reflectObj1.print();
            Constructor<ReflectObj> constructor=clazz1.getConstructor(String.class);//获取带参数的构造方法
            reflectObj1=constructor.newInstance("带参数的构造");
            reflectObj1.print();
        } catch (Exception e) {
            e.printStackTrace();
        }
    }
}

class ReflectObj{
    private String name;
    public String namePublic;

    public ReflectObj() {
    }

    public ReflectObj(String name) {
        this.name = name;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public void print(){
        System.out.println("print输出 "+name);
    }
}
